package ant.tool;

import org.apache.tools.ant.Task;
import org.apache.tools.ant.types.Path;
import org.dom4j.Document;
import org.dom4j.Element;
import org.dom4j.io.OutputFormat;
import org.dom4j.io.SAXReader;
import org.dom4j.io.XMLWriter;

import java.io.FileOutputStream;
import java.io.OutputStreamWriter;
import java.util.Iterator;
import java.util.List;

/**
 * 将两个XML文件内容合并,并将同类型节点放在一起的Ant task.
 * 比如,web.xml要求相同类型的节点如<context-param>,<filter> 放在一起.
 *
 * @author calvin
 */
public class XmlMergeTask extends Task {
    private Path metaFile;

    private Path destFile;

    private String nodes;

    public void setMetaFile(Path metaFile) {
        this.metaFile = metaFile;
    }

    public void setDestFile(Path destFile) {
        this.destFile = destFile;
    }

    public void setNodes(String nodes) {
        this.nodes = nodes;
    }

    public void execute() {
        try {
            SAXReader mReader = new SAXReader();
            mReader.setEncoding("UTF-8");
            SAXReader dReader = new SAXReader();
            dReader.setEncoding("UTF-8");
            Document mDocument = mReader.read(metaFile.list()[0]);
            Document dDocument = dReader.read(destFile.list()[0]);
            Element mRoot = mDocument.getRootElement();
            Element dRoot = dDocument.getRootElement();
            String[] nodeNameList = nodes.split(",");
            for (String nodeName : nodeNameList)
                merge(dRoot, mRoot, nodeName);

            OutputFormat format = OutputFormat.createPrettyPrint();
            format.setEncoding("UTF-8");
            format.setIndentSize(4);
            FileOutputStream fs = new FileOutputStream(destFile.list()[0]);

            XMLWriter writer = new XMLWriter(new OutputStreamWriter(fs, "UTF-8"), format);

            writer.write(dDocument);
            writer.close();
        } catch (Exception e) {
            System.out.println(e.getMessage());
        }
    }

    private void merge(Element dRoot, Element mRoot, String filterName) {
        List dFilterlist = dRoot.elements(filterName);
        for (Iterator i = mRoot.elementIterator(filterName); i.hasNext();) {
            Element element = (Element) i.next();
            element.setParent(null);
            dFilterlist.add(dFilterlist.size(), element);
        }
    }

}
